﻿using System;
using System.Collections;
using System.Collections.Generic;
using System.ComponentModel.Design;
using System.Diagnostics;
using System.Drawing;
using System.IO;
using System.Linq;
using System.Security.Permissions;
using System.Windows.Forms;

using Microsoft.VisualStudio;
using Microsoft.VisualStudio.Shell;
using Microsoft.VisualStudio.Shell.Interop;

using Wicresoft.Shell.Core;
using Wicresoft.Shell.Data;
using Wicresoft.Shell.Logic;

namespace Wicresoft.Shell.Package.AppExp
{
    /// <summary>
    /// Summary description for MyControl.
    /// </summary>
    public partial class MyControl : UserControl
    {
        private TreeNode cutNode;
        public TreeNode selectedNode = null;
        private MyToolWindow parent;

        private static object syncObj = new object();

        // The dictionary contains all created temp source files.
        // The key is the id of the node. The value is the path to the temp file.
        private Dictionary<string, string> tempSourceFileDictionary = new Dictionary<string, string>();

        // A list of watchers, put them in a list in order to avoid being collected by GC.
        private List<FileSystemWatcher> watchers = new List<FileSystemWatcher>();

        public MyControl(MyToolWindow parent)
        {
            InitializeComponent();
            GlobalData.myControl = this;
            this.parent = parent;

            treeView1.DoubleClick += new EventHandler(treeView1_DoubleClick);
        }

        //double click = view code
        private void treeView1_DoubleClick(object sender, EventArgs e)
        {
            object tag = this.treeView1.SelectedNode.Tag;
            if (tag != null)
            {
                //only function prof node has ';' 
                if (tag.ToString().Contains(';'))
                {
                    //Logger.Output(tag.ToString());
                    viewCodeToolStripMenuItem_Click(this, null);
                }
            }
        }


        /// <summary> 
        /// Let this control process the mnemonics.
        /// </summary>
        [UIPermission(SecurityAction.LinkDemand, Window = UIPermissionWindow.AllWindows)]
        protected override bool ProcessDialogChar(char charCode)
        {
            // If we're the top-level form or control, we need to do the mnemonic handling
            if (charCode != ' ' && ProcessMnemonic(charCode))
            {
                return true;
            }
            return base.ProcessDialogChar(charCode);
        }

        /// <summary>
        /// Enable the IME status handling for this control.
        /// </summary>
        protected override bool CanEnableIme
        {
            get
            {
                return true;
            }
        }

        [System.Diagnostics.CodeAnalysis.SuppressMessage("Microsoft.Globalization", "CA1300:SpecifyMessageBoxOptions")]
        private void button1_Click(object sender, System.EventArgs e)
        {
            MessageBox.Show(this,
                            string.Format(System.Globalization.CultureInfo.CurrentUICulture, "We are inside {0}.button1_Click()", this.ToString()),
                            "Application Explorer");
        }

        private void BuildTreeView()
        {
            Debug.Assert(null != Workspace.GetDatabaseLogic(), "database must be set before call BuildTreeView()");

            this.treeView1.Nodes.Clear();
            IEnumerable<ApplicationTable> appData = Workspace.GetDatabaseLogic().GetApplicationTableData();
            IEnumerable<FunctionTable> funData = Workspace.GetDatabaseLogic().GetFunctionTableData();
            //Add application tree node
            List<ApplicationTable> nodes = new List<ApplicationTable>();
            foreach (ApplicationTable row in appData)
            {
                nodes.Add(row);
            }
            while (nodes.Count > 0)
            {
                for (int i = 0; i < nodes.Count; i++)
                {
                    Logger.Output("enum to App :" + nodes[i].APP_NAME);
                    IEnumerable<ApplicationProfTable> appProf = Workspace.GetDatabaseLogic().GetApplicationProfTableDataByAppID(nodes[i].APP_ID);
                    TreeNode current = null;
                    if (nodes[i].APP_FATHER_ID != null)
                    {
                        TreeNode node = SearchTree(nodes[i].APP_FATHER_ID.ToString(), treeView1.Nodes);
                        if (null != node)
                        {
                            node.Nodes[0].Nodes.Add(nodes[i].APP_ID.ToString(), nodes[i].APP_NAME, 
                                (int)AppExpImageList.Application, (int)AppExpImageList.ApplicationSelected);
                            current = node.Nodes[0].Nodes[nodes[i].APP_ID.ToString()];
                            current.Tag = nodes[i].APP_ID.ToString();
                            BuildTreeNodeGroup(current);
                            nodes.RemoveAt(i);
                        }
                    }
                    else
                    {
                        treeView1.Nodes.Add(nodes[i].APP_ID.ToString(), nodes[i].APP_NAME,
                            (int)AppExpImageList.Application, (int)AppExpImageList.ApplicationSelected);
                        current = treeView1.Nodes[nodes[i].APP_ID.ToString()];
                        current.Tag = nodes[i].APP_ID.ToString();
                        BuildTreeNodeGroup(current);
                        nodes.RemoveAt(i);
                    }

                    foreach (ApplicationProfTable row in appProf)
                    {
                        try
                        {
                            if (row.APP_PROF_TYPE == "xsl")
                            {
                                TreeNode ExNode = new TreeNode(row.APP_PROF_NAME,
                                    (int)AppExpImageList.TempXslt, (int)AppExpImageList.TempXsltSelected);
                                ExNode.Tag = "APIDXX" + string.Format("{0};{1}", current.Tag.ToString(), row.APP_PROF_ID);
                                current.Nodes[2].Nodes.Add(ExNode);
                            }
                            else if (row.APP_PROF_TYPE == "vm")
                            {
                                TreeNode ExNode = new TreeNode(row.APP_PROF_NAME,
                                    (int)AppExpImageList.TempVm, (int)AppExpImageList.TempVmSelected);
                                ExNode.Tag = "APIDXV" + string.Format("{0};{1}", current.Tag.ToString(), row.APP_PROF_ID);
                                current.Nodes[2].Nodes.Add(ExNode);
                            }
                            else if (row.APP_PROF_TYPE == "txt")
                            {
                                TreeNode ExNode = new TreeNode(row.APP_PROF_NAME,
                                    (int)AppExpImageList.TempTxt, (int)AppExpImageList.TempTxtSelected);
                                ExNode.Tag = "APIDXT" + string.Format("{0};{1}", current.Tag.ToString(), row.APP_PROF_ID);
                                current.Nodes[2].Nodes.Add(ExNode);
                            }
                            else if(row.APP_PROF_TYPE == "html")
                            {
                                TreeNode ExNode = new TreeNode(row.APP_PROF_NAME,
                                    (int)AppExpImageList.TempHtml, (int)AppExpImageList.TempHtmlSelected);
                                ExNode.Tag = "APIDXH" + string.Format("{0};{1}", current.Tag.ToString(), row.APP_PROF_ID);
                                current.Nodes[2].Nodes.Add(ExNode);
                            }
                        }
                        catch (Exception e)
                        {
                            MessageBox.Show(e.Message);
                        }
                    }
                }
            }
            //Add function tree node
            foreach (FunctionTable function in funData)
            {
                //find parent app node
                Logger.Output("enum to function :" + function.FUNCTION_NAME);
                TreeNode node = SearchTree(function.APP_ID.ToString(), treeView1.Nodes);
                if (null != node)
                {
                    string funID = "FID" + function.FUNCTION_ID;
                    node.Nodes[1].Nodes.Add(funID, function.FUNCTION_NAME,
                        (int)AppExpImageList.Function, (int)AppExpImageList.FunctionSelected);
                    node.Nodes[1].Nodes[funID].Tag = funID.ToString();
                    ////no basicTemp , just use AdapterType
                    //TreeNode AdapterTypeNode = new TreeNode(Resources.AdapterType,
                    //    (int)AppExpImageList.Templates, (int)AppExpImageList.TemplatesSelected);
                    //TreeNode dataTempNode = new TreeNode(Resources.DataTemp,
                    //    (int)AppExpImageList.Templates, (int)AppExpImageList.TemplatesSelected);
                    //TreeNode adapterTempNode = new TreeNode(Resources.AdapterTemp,
                    //    (int)AppExpImageList.Templates, (int)AppExpImageList.TemplatesSelected);
                    //TreeNode xslTempNode = new TreeNode(Resources.ExProf,
                    //    (int)AppExpImageList.ExProfCat, (int)AppExpImageList.ExProfCatSelected);
                    //node.Nodes[1].Nodes[funID].Nodes.AddRange(new TreeNode[] {
                    //                    AdapterTypeNode,
                    //                    dataTempNode,
                    //                    adapterTempNode,
                    //                    xslTempNode});
                    FillFunctionStructure(node.Nodes[1].Nodes[funID]);
                    //Add function tree leaf
                    IEnumerable<FunctionProfTable> functionProf = Workspace.GetDatabaseLogic().GetFunctionProfTableDataByFuncID(function.FUNCTION_ID);
                    foreach (FunctionProfTable row in functionProf)
                    {
                        /*modify by parker :
                          for the issue Id#4386 delete extension .xml .xsl .umc
                          for the issue Id#4388  change the tag to distribute basic\data\moblie_template\xsl,this change may cause some other problem*/
                        if (row.FUNC_PROF_NAME == "BASIC_TEMPLATE")
                        {
                            TreeNode basicFileNode = new TreeNode("Basic.xml",
                                (int)AppExpImageList.TempBasic, (int)AppExpImageList.TempBasicSelected);
                            basicFileNode.Tag = "FPIDB" + string.Format("{0};{1}", function.FUNCTION_ID, row.FUNC_PROF_ID);
                            node.Nodes[1].Nodes[funID].Nodes[0].Nodes.Add(basicFileNode);
                        }
                        //data template
                        if (row.FUNC_PROF_NAME == "DATA_TEMPLATE")
                        {
                            TreeNode dataFileNode = new TreeNode("Data",
                                (int)AppExpImageList.TempData, (int)AppExpImageList.TempDataSelected);
                            dataFileNode.Tag = "FPIDD" + string.Format("{0};{1}", function.FUNCTION_ID, row.FUNC_PROF_ID);
                            node.Nodes[1].Nodes[funID].Nodes[1].Nodes.Add(dataFileNode);
                        }
                        //adpter template
                        else if (row.FUNC_PROF_NAME == "MOBILE_TEMPLATE")
                        {
                            string fileName = string.Format("{0}", row.CLIENT_SYS_TYPE);
                            TreeNode adapterFileNode = new TreeNode(fileName,
                                (int)AppExpImageList.TempAdapter, (int)AppExpImageList.TempAdapterSelected);
                            adapterFileNode.Tag = "FPIDM" + string.Format("{0};{1}", function.FUNCTION_ID, row.FUNC_PROF_ID);
                            node.Nodes[1].Nodes[funID].Nodes[2].Nodes.Add(adapterFileNode);
                        }
                        //extension prof : xsl
                        else if (row.FUNC_PROF_TYPE == "xsl")
                        {
                            TreeNode ExNode = new TreeNode(row.FUNC_PROF_NAME,
                                (int)AppExpImageList.TempXslt, (int)AppExpImageList.TempXsltSelected);
                            ExNode.Tag = "FPIDXX" + string.Format("{0};{1}", function.FUNCTION_ID, row.FUNC_PROF_ID);
                            node.Nodes[1].Nodes[funID].Nodes[3].Nodes.Add(ExNode);
                        }
                        //extension prof : vm
                        else if (row.FUNC_PROF_TYPE == "vm")
                        {
                            TreeNode ExNode = new TreeNode(row.FUNC_PROF_NAME,
                                (int)AppExpImageList.TempVm, (int)AppExpImageList.TempVmSelected);
                            ExNode.Tag = "FPIDXV" + string.Format("{0};{1}", function.FUNCTION_ID, row.FUNC_PROF_ID);
                            node.Nodes[1].Nodes[funID].Nodes[3].Nodes.Add(ExNode);
                        }
                        //extension prof : txt
                        else if (row.FUNC_PROF_TYPE == "txt")
                        {
                            TreeNode ExNode = new TreeNode(row.FUNC_PROF_NAME,
                                (int)AppExpImageList.TempTxt, (int)AppExpImageList.TempTxtSelected);
                            ExNode.Tag = "FPIDXT" + string.Format("{0};{1}", function.FUNCTION_ID, row.FUNC_PROF_ID);
                            node.Nodes[1].Nodes[funID].Nodes[3].Nodes.Add(ExNode);
                        }
                        //extension prof : html
                        else if (row.FUNC_PROF_TYPE == "html")
                        {
                            TreeNode ExNode = new TreeNode(row.FUNC_PROF_NAME,
                                (int)AppExpImageList.TempHtml, (int)AppExpImageList.TempHtmlSelected);
                            ExNode.Tag = "FPIDXH" + string.Format("{0};{1}", function.FUNCTION_ID, row.FUNC_PROF_ID);
                            node.Nodes[1].Nodes[funID].Nodes[3].Nodes.Add(ExNode);
                        }
                        //else if (row.FUNC_PROF_VALUE.StartsWith("<"))
                        //{
                        //    TreeNode xslFileNode = new TreeNode(row.FUNC_PROF_NAME,
                        //        (int)AppExpImageList.TempXslt, (int)AppExpImageList.TempXsltSelected);
                        //    xslFileNode.Tag = "FPIDX" + string.Format("{0};{1}", function.FUNCTION_ID, row.FUNC_PROF_ID);
                        //    node.Nodes[1].Nodes[funID].Nodes[3].Nodes.Add(xslFileNode);
                        //}
                    }
                }
            }
        }

        private TreeNode SearchTree(string key, TreeNodeCollection nodes)
        {
            TreeNode node = null;

            if (nodes.IndexOfKey(key) >= 0)
            {
                node = nodes[key];
            }
            else
            {
                foreach (TreeNode treeNode in nodes)
                {
                    node = SearchTree(key, treeNode.Nodes);
                    if (null != node)
                    {
                        break;
                    }
                }
            }
            return node;
        }

        private TreeNode SearchTreeByTag(string tag, TreeNodeCollection nodes)
        {
            TreeNode node = null;
            foreach(TreeNode tn in nodes)
            {
                if (tn.Tag != null)
                {
                    if (tn.Tag.ToString() == tag)
                    {
                        node = tn;
                        break;
                    }
                }
            }
            if(node == null)
            {
                foreach (TreeNode treeNode in nodes)
                {
                    node = SearchTreeByTag(tag, treeNode.Nodes);
                    if (null != node)
                    {
                        break;
                    }
                }
            }

            return node;
        }

        //when a new function is added , we need add some folders for it in default.
        private void FillFunctionStructure(TreeNode node)
        {
            //no basicTemp , just use AdapterType
            TreeNode AdapterTypeNode = new TreeNode(Resources.AdapterType,
                (int)AppExpImageList.Templates, (int)AppExpImageList.TemplatesSelected);
            TreeNode dataTempNode = new TreeNode(Resources.DataTemp,
                (int)AppExpImageList.Templates, (int)AppExpImageList.TemplatesSelected);
            TreeNode adapterTempNode = new TreeNode(Resources.AdapterTemp,
                (int)AppExpImageList.Templates, (int)AppExpImageList.TemplatesSelected);
            TreeNode xslTempNode = new TreeNode(Resources.ExProf,
                (int)AppExpImageList.ExProfCat, (int)AppExpImageList.ExProfCatSelected);
            node.Nodes.AddRange(new TreeNode[]{
                AdapterTypeNode,
                dataTempNode,
                adapterTempNode,
                xslTempNode
            });

        }

        //when a new application is added , we need add some folders for it in default.
        private void BuildTreeNodeGroup(TreeNode node)
        {
            TreeNode subAppNode = new TreeNode(Resources.SubAppNode,
                (int)AppExpImageList.AppCat, (int)AppExpImageList.AppCatSelected);
            TreeNode functionNode = new TreeNode(Resources.FunctionNode,
                (int)AppExpImageList.FunCat, (int)AppExpImageList.FunCatSelected);
            //add extension prof
            TreeNode extensionProfNode = new TreeNode(Resources.ExProf,
                (int)AppExpImageList.ExProfCat, (int)AppExpImageList.ExProfCatSelected);

            node.Nodes.Add(subAppNode);
            node.Nodes.Add(functionNode);
            node.Nodes.Add(extensionProfNode);
        }

        private void SetStripMenuItem(TreeNode currentNode)
        {
            foreach (ToolStripItem menuItem in this.contextMenuStrip1.Items)
            {
                menuItem.Visible = false;
            }
            if (currentNode.Tag != null)
            {
                /*distribute the right click menu for basic\data\moblie_template\xsl*/
                if (currentNode.Tag.ToString().StartsWith("FID"))
                {
                    //this.addDataTempToolStripMenuItem.Visible = true;
                    //this.addAdapterTempToolStripMenuItem.Visible = true;
                    //this.addXSLTempToolStripMenuItem.Visible = true;
                    this.AddFunctionProf.Visible = true;
                    this.AddTemplateToolStripMenuItem.Visible = true;
                    this.toolStripSeparator1.Visible = true;
                    this.cutToolStripMenuItem.Visible = true;
                    this.copyToolStripMenuItem.Visible = true;
                    this.pasteToolStripMenuItem.Visible = false;
                    this.deleteToolStripMenuItem.Visible = true;
                    this.toolStripSeparator2.Visible = true;
                    //this.propertyToolStripMenuItem.Visible = true;
                }
                //basic template
                else if (currentNode.Tag.ToString().StartsWith("FPIDB"))
                {
                }
                //data template
                else if (currentNode.Tag.ToString().StartsWith("FPIDD"))
                {
                    this.viewCodeToolStripMenuItem.Visible = true;
                    this.viewCodeToolStripMenuItem.Enabled = true;
                    this.toolStripSeparator3.Visible = true;
                    this.deleteToolStripMenuItem.Visible = true;
                    this.toolStripSeparator2.Visible = true;
                    //this.propertyToolStripMenuItem.Visible = true;
                }
                //mobile template
                else if (currentNode.Tag.ToString().StartsWith("FPIDM"))
                {
                    this.viewCodeToolStripMenuItem.Visible = true;
                    this.viewCodeToolStripMenuItem.Enabled = true;
                    this.viewDesignToolStripMenuItem.Visible = true;
                    this.viewDesignToolStripMenuItem.Enabled = true;
                    this.toolStripSeparator3.Visible = true;
                    this.deleteToolStripMenuItem.Visible = true;
                    this.toolStripSeparator2.Visible = true;
                    //this.propertyToolStripMenuItem.Visible = true;
                }
                //function extension template
                else if (currentNode.Tag.ToString().StartsWith("FPIDX"))
                {
                    this.viewCodeToolStripMenuItem.Visible = true;
                    this.viewCodeToolStripMenuItem.Enabled = true;
                    this.toolStripSeparator3.Visible = true;
                    this.deleteToolStripMenuItem.Visible = true;
                    this.toolStripSeparator2.Visible = true;
                    //this.propertyToolStripMenuItem.Visible = true;
                }
                //app extension template
                else if (currentNode.Tag.ToString().StartsWith("APIDX"))
                {
                    this.viewCodeToolStripMenuItem.Visible = true;
                    this.viewCodeToolStripMenuItem.Enabled = true;
                    this.toolStripSeparator3.Visible = true;
                    this.deleteToolStripMenuItem.Visible = true;
                    this.toolStripSeparator2.Visible = true;
                    //this.propertyToolStripMenuItem.Visible = true;
                }
                else
                {
                    this.addSubApplicationToolStripMenuItem.Visible = true;
                    this.addFunctionMenuItem.Visible = true;
                    this.AddAppProf.Visible = true;
                    this.toolStripSeparator4.Visible = true;
                    this.cutToolStripMenuItem.Visible = true;
                    this.copyToolStripMenuItem.Visible = true;
                    this.pasteToolStripMenuItem.Visible = true;
                    this.deleteToolStripMenuItem.Visible = true;
                    this.toolStripSeparator2.Visible = true;
                    //this.propertyToolStripMenuItem.Visible = true;
                }
            }
        }

        //deal with delete command
        private void deleteToolStripMenuItem_Click(object sender, System.EventArgs e)
        {
            if (MessageBox.Show(Resources.DelNodeText, Resources.DelNodeCaption, MessageBoxButtons.OKCancel) == DialogResult.OK)
            {
                TreeNode node = treeView1.SelectedNode;
                string t_tag = node.Tag.ToString();
                //MessageBox.Show(t_tag);
                //if target is a function
                try
                {
                    if (t_tag.StartsWith("FID"))
                    {
                        string function_ID = t_tag.Substring(3);
                        Workspace.GetDatabaseLogic().DeleteFunctionTableDataByID(Convert.ToInt16(function_ID));
                    }
                    else if (t_tag.StartsWith("FPIDX"))
                    {
                        string t_str = t_tag.Substring(6);
                        string[] ids = t_str.Split(';');
                        Workspace.GetDatabaseLogic().DeleteFunctionProfByFunctionIDAndProfID(Convert.ToInt16(ids[0]), Convert.ToInt16(ids[1]));
                    }
                    //if target is a template
                    else if (t_tag.StartsWith("FPID"))
                    {
                        string t_str = t_tag.Substring(5);
                        string[] ids = t_str.Split(';');
                        Workspace.GetDatabaseLogic().DeleteFunctionProfByFunctionIDAndProfID(Convert.ToInt16(ids[0]), Convert.ToInt16(ids[1]));
                    }
                    //if target is a application extension prof
                    else if (t_tag.StartsWith("APIDX"))
                    {
                        string t_str = t_tag.Substring(6);
                        string[] ids = t_str.Split(';');
                        Workspace.GetDatabaseLogic().DeleteApplicationProfByAppIDAndProfID(Convert.ToInt16(ids[0]), Convert.ToInt16(ids[1]));
                    }
                    //else the target is a appliacation
                    else
                    {
                        Workspace.GetDatabaseLogic().DeleteAppTableDataByID(Convert.ToInt16(t_tag));
                    }
                    treeView1.Nodes.Remove(node);
                }
                catch{
                    MessageBox.Show("删除失败！","提示",MessageBoxButtons.OK);
                }
            }
        }

        //to enum the children nodes to change the image
        private void CheckChildrenNodesImage(TreeNode node)
        {
            string temp_tag = string.Empty;
            foreach (TreeNode nd in node.Nodes)
            {
                ChangeImageForNode(nd);
                if (nd.Nodes.Count > 0)
                    CheckChildrenNodesImage(nd);
            }
        }

        //change a single node image
        private void ChangeImageForNode(TreeNode nd)
        {
            string temp_tag = string.Empty;
            //may appcat node or functioncat node or template
            if (nd.Tag == null)
            {
                if (nd.Text == Resources.SubAppNode)
                {
                    nd.ImageIndex = (int)AppExpImageList.AppCat;
                    nd.SelectedImageIndex = (int)AppExpImageList.AppCatSelected;             
                }
                else if (nd.Text == Resources.FunctionNode)
                {
                    nd.ImageIndex = (int)AppExpImageList.FunCat;
                    nd.SelectedImageIndex = (int)AppExpImageList.FunCatSelected;
                }
                else if(nd.Text == Resources.ExProf)
                {
                    nd.ImageIndex = (int)AppExpImageList.ExProfCat;
                    nd.SelectedImageIndex = (int)AppExpImageList.ExProfCatSelected;
                }
                else
                {
                    nd.ImageIndex = (int)AppExpImageList.Templates;
                    nd.SelectedImageIndex = (int)AppExpImageList.TemplatesSelected;
                }
            }
            else
            {
                temp_tag = nd.Tag.ToString();
                if (temp_tag.StartsWith("FID"))
                {
                    nd.ImageIndex = (int)AppExpImageList.Function;
                    nd.SelectedImageIndex = (int)AppExpImageList.FunctionSelected;
                }
                else if (temp_tag.StartsWith("FPIDB"))
                {
                    nd.ImageIndex = (int)AppExpImageList.TempBasic;
                    nd.SelectedImageIndex = (int)AppExpImageList.TempBasicSelected;
                }
                else if (temp_tag.StartsWith("FPIDD"))
                {
                    nd.ImageIndex = (int)AppExpImageList.TempData;
                    nd.SelectedImageIndex = (int)AppExpImageList.TempDataSelected;
                }
                else if (temp_tag.StartsWith("FPIDM"))
                {
                    nd.ImageIndex = (int)AppExpImageList.TempAdapter;
                    nd.SelectedImageIndex = (int)AppExpImageList.TempAdapterSelected;
                }
                else if (temp_tag.StartsWith("FPIDXX"))
                {
                    nd.ImageIndex = (int)AppExpImageList.TempXslt;
                    nd.SelectedImageIndex = (int)AppExpImageList.TempXsltSelected;
                }
                else if (temp_tag.StartsWith("FPIDXV"))
                {
                    nd.ImageIndex = (int)AppExpImageList.TempVm;
                    nd.SelectedImageIndex = (int)AppExpImageList.TempVmSelected;
                }
                else if (temp_tag.StartsWith("FPIDXT"))
                {
                    nd.ImageIndex = (int)AppExpImageList.TempTxt;
                    nd.SelectedImageIndex = (int)AppExpImageList.TempTxtSelected;
                }
                else if (temp_tag.StartsWith("FPIDXH"))
                {
                    nd.ImageIndex = (int)AppExpImageList.TempHtml;
                    nd.SelectedImageIndex = (int)AppExpImageList.TempHtmlSelected;
                }
                else if (temp_tag.StartsWith("APIDXX"))
                {
                    nd.ImageIndex = (int)AppExpImageList.TempXslt;
                    nd.SelectedImageIndex = (int)AppExpImageList.TempXsltSelected;
                }
                else if (temp_tag.StartsWith("APIDXV"))
                {
                    nd.ImageIndex = (int)AppExpImageList.TempVm;
                    nd.SelectedImageIndex = (int)AppExpImageList.TempVmSelected;
                }
                else if (temp_tag.StartsWith("APIDXT"))
                {
                    nd.ImageIndex = (int)AppExpImageList.TempTxt;
                    nd.SelectedImageIndex = (int)AppExpImageList.TempTxtSelected;
                }
                else if (temp_tag.StartsWith("APIDXH"))
                {
                    nd.ImageIndex = (int)AppExpImageList.TempHtml;
                    nd.SelectedImageIndex = (int)AppExpImageList.TempHtmlSelected;
                }
                else
                {
                    nd.ImageIndex = (int)AppExpImageList.Application;
                    nd.SelectedImageIndex = (int)AppExpImageList.ApplicationSelected;
                }
            }
        }

        // BUGBUG: Below method has a defect, currently there are three types of node tags:
        // FID, FPID, empty(means app ID). But below method only consider two types.
        //Modify code for cut/copy functions;Review code: SunRui
        private void pasteToolStripMenuItem_Click(object sender, System.EventArgs e)
        {
            string app_ID = "0";
            string function_ID = "0";
            string current_ID = "0";
            bool copyFlag = false;
            string NodeName;
            TreeNode node = (TreeNode)Clipboard.GetData("TreeNode");
            
            bool currentType = treeView1.SelectedNode.Tag.ToString().StartsWith("FID");
            bool clipBoardType = node.Tag.ToString().StartsWith("FID");
            if (cutNode == null)
            {
                //node.Text = node.Text + " - Copy";
                copyFlag = true;
            }

            if (treeView1.SelectedNode != null)
            {
                current_ID = treeView1.SelectedNode.Tag.ToString();
                Logger.Output(string.Format("ID:{0}", node.Tag.ToString()));
                //if function to be added
                if (clipBoardType)
                {
                    function_ID = node.Tag.ToString().Substring(3);
                    Logger.Output(string.Format("FID:{0}&{1}", function_ID, current_ID));

                    if (copyFlag)
                    {
                        NodeName = Workspace.GetDatabaseLogic().CopyFunctionNode(Convert.ToInt32(function_ID), Convert.ToInt32(current_ID));
                    }
                    else
                    {
                        NodeName = Workspace.GetDatabaseLogic().CutFunctionNode(Convert.ToInt32(function_ID), Convert.ToInt32(current_ID));
                    }
                    //node.Text = NodeName;
                    ////fix the image problem
                    //node.ImageIndex = (int)AppExpImageList.Function;
                    //node.SelectedImageIndex = (int)AppExpImageList.FunctionSelected;
                    //CheckChildrenNodesImage(node);
                    ////

                    //treeView1.SelectedNode.Nodes[1].Nodes.Add(node);

                }
                //if application to be added
                else
                {
                    app_ID = node.Tag.ToString();
                    Logger.Output(string.Format("AppID:{0}&{1}", app_ID, current_ID));

                    if (copyFlag)
                    {
                        NodeName = Workspace.GetDatabaseLogic().CopyApplicationNode(Convert.ToInt32(app_ID), Convert.ToInt32(current_ID));

                    }
                    else
                    {
                        NodeName = Workspace.GetDatabaseLogic().CutApplicationNode(Convert.ToInt32(app_ID), Convert.ToInt32(current_ID));
                    }

                    //node.Text = NodeName;
                    ////fix the image problem
                    //node.ImageIndex = (int)AppExpImageList.Application;
                    //node.SelectedImageIndex = (int)AppExpImageList.ApplicationSelected;
                    //CheckChildrenNodesImage(node);
                    ////

                    //treeView1.SelectedNode.Nodes[0].Nodes.Add(node);


                }
                BuildTreeView();
                this.SelectAndExpandOrOpen(current_ID);
                

                //treeView1.SelectedNode.Expand();
                if (cutNode != null)
                {
                    cutNode.Remove();
                    cutNode = null;
                }
                //BuildTreeView();
                treeView1.SelectedNode = treeView1.SelectedNode.LastNode;
                
            }
        }

        private void copyToolStripMenuItem_Click(object sender, System.EventArgs e)
        {
            TreeNode node = treeView1.SelectedNode;
            Clipboard.SetData("TreeNode", node);
        }

        private void cutToolStripMenuItem_Click(object sender, System.EventArgs e)
        {
            TreeNode node = treeView1.SelectedNode;
            Clipboard.SetData("TreeNode", node);
            cutNode = node;
        }

        private void openToolStripMenuItem_Click(object sender, System.EventArgs e)
        {
            MessageBox.Show("Open");
        }

        private void SelectAndExpandOrOpen(string tag)
        {
            treeView1.SelectedNode = SearchTreeByTag(tag, treeView1.Nodes);
            if (tag.StartsWith("FPID") || tag.StartsWith("APIDX"))
            {
                ShowWindowFrame(CreateTempSourceFile(false), VSConstants.LOGVIEWID_Code);
            }
            else
            {
                if(treeView1.SelectedNode != null)
                    treeView1.SelectedNode.Expand();
            }
        }

        private void addSubApplicationToolStripMenuItem_Click(object sender, System.EventArgs e)
        {
            using (NewItemForm dialog = new NewItemForm("Application"))
            {
                //dialog.categoryTV.SelectedNode = dialog.categoryTV.Nodes[0];
                dialog.ShowDialog();
                if (dialog.DialogResult == DialogResult.OK)
                {
                    int lastid = 0;
                    List<ApplicationTable> appData = new List<ApplicationTable>();
                    ApplicationTable data = new ApplicationTable();
                    data.IS_LEAF = 1;
                    data.APP_FATHER_ID = Convert.ToInt32(this.selectedNode.Tag.ToString());
                    data.APP_NAME = dialog.nameTB.Text;
                    data.APP_DESC = dialog.descriptionTB.Text;
                    data.APP_CODE = string.Empty;
                    appData.Add(data);
                    Workspace.GetDatabaseLogic().InsertApplicationTableData(appData, ref lastid);

                    //update the tree in area instead refresh the whole tree
                    this.selectedNode.Nodes[0].Nodes.Add(lastid.ToString(), data.APP_NAME,
                        (int)AppExpImageList.Application, (int)AppExpImageList.ApplicationSelected);
                    selectedNode.Nodes[0].Nodes[lastid.ToString()].Tag = lastid.ToString();
                    BuildTreeNodeGroup(selectedNode.Nodes[0].Nodes[lastid.ToString()]);

                    //BuildTreeView();
                    SelectAndExpandOrOpen(lastid.ToString());
                }
            }
        }

        private void addFunctionMenuItem_Click(object sender, System.EventArgs e)
        {
            using (NewItemForm dialog = new NewItemForm("Function"))
            {
                //dialog.categoryTV.SelectedNode = dialog.categoryTV.Nodes[1];
                dialog.ShowDialog();
                if (dialog.DialogResult == DialogResult.OK)
                {
                    int lastid = 0;
                    List<FunctionTable> funData = new List<FunctionTable>();
                    FunctionTable data = new FunctionTable();
                    data.APP_ID = Convert.ToInt32(this.selectedNode.Tag.ToString());
                    data.FUNCTION_NAME = dialog.nameTB.Text;
                    data.FUNCTION_DESC = dialog.descriptionTB.Text;
                    data.FUNCTION_CODE = dialog.txtFunctionCode.Text;
                    funData.Add(data);
                    Workspace.GetDatabaseLogic().InsertFunctionTableData(funData, ref lastid);
                    //update the tree in area instead refresh the whole tree
                    this.selectedNode.Nodes[1].Nodes.Add(lastid.ToString(), data.FUNCTION_NAME,
                        (int)AppExpImageList.Function, (int)AppExpImageList.FunctionSelected);
                    selectedNode.Nodes[1].Nodes[lastid.ToString()].Tag = "FID" + lastid.ToString();
                    FillFunctionStructure(selectedNode.Nodes[1].Nodes[lastid.ToString()]);
                    //BuildTreeView();
                    SelectAndExpandOrOpen("FID" + lastid.ToString());
                }
            }
        }



        private void propertyToolStripMenuItem_Click(object sender, System.EventArgs e)
        {
            /*
            IVsUIShell shell = GetService(typeof(SVsUIShell)) as IVsUIShell;
            if (null != shell)
            {
                IVsWindowFrame confWindowFrame = null;
                Guid guid = new Guid("43723E33-D911-40ae-B40E-AD0F685C3D9A");
                shell.FindToolWindow((uint)__VSFINDTOOLWIN.FTW_fForceCreate, ref guid, out confWindowFrame);
                if (null != confWindowFrame)
                {
                    confWindowFrame.SetProperty((int)__VSFPROPID.VSFPROPID_FrameMode, VSFRAMEMODE.VSFM_MdiChild);
                    confWindowFrame.Show();
                }
            }
             */

            //DisplayProperty();

        }

        private void DisplayProperty()
        {
            ArrayList mySelItems = new ArrayList();
            IVsUIShell shell = GetService(typeof(SVsUIShell)) as IVsUIShell;
            if (null != shell)
            {
                IVsWindowFrame confWindowFrame = null;
                Guid guid = new Guid(ToolWindowGuids.PropertyBrowser);
                shell.FindToolWindow((uint)__VSFINDTOOLWIN.FTW_fForceCreate, ref guid, out confWindowFrame);

                SelectionContainer mySelectionContainer = new SelectionContainer();

                //MyPropertyItem item = new MyPropertyItem(this, treeView1.SelectedNode.Text);
                PropertyWindowManager pwm = new PropertyWindowManager(treeView1.SelectedNode);

                mySelItems.Add(pwm.GetPropertyItemObject());

                //if (pwm.GetPropertyItemObject() != null)
                //{
                //    mySelItems.Add(item);
                //}

                mySelectionContainer.SelectedObjects = mySelItems;
                ITrackSelection track = GetService(typeof(STrackSelection)) as ITrackSelection;
                if (track != null)
                {
                    track.OnSelectChange(mySelectionContainer);
                }
            }
        }

        protected override object GetService(Type service)
        {
            object obj = null;
            if (parent != null)
            {
                obj = parent.GetvsService(service);
            }
            if (obj == null)
            {
                obj = base.GetService(service);
            }
            return obj;
        }

        private void treeView1_MouseDown(object sender, MouseEventArgs e)
        {
            Point clickPoint = new Point(e.X, e.Y);
            TreeNode currentNode = treeView1.GetNodeAt(clickPoint);
            if (null != currentNode)
            {
                if (e.Button == MouseButtons.Right)
                {
                    SetStripMenuItem(currentNode);
                    currentNode.ContextMenuStrip = this.contextMenuStrip1;
                }
                if (treeView1.SelectedNode == currentNode)
                {
                    //treeView1.LabelEdit = true;
                }
                treeView1.SelectedNode = currentNode;
                this.selectedNode = currentNode;
                this.parent.propertyCommand.Enabled = (this.selectedNode.Tag != null);
            }
        }

        private void treeView1_AfterLabelEdit(object sender, NodeLabelEditEventArgs e)
        {
            if (null != e.Label)
            {
                if (e.Label == string.Empty)
                {
                    MessageBox.Show("You must enter a name.");
                    e.CancelEdit = true;
                    e.Node.BeginEdit();
                }
            }
            else
            {
                treeView1.LabelEdit = false;
            }
        }

        private void viewDesignToolStripMenuItem_Click(object sender, EventArgs e)
        {
            ShowWindowFrame(CreateTempSourceFile(false), VSConstants.LOGVIEWID_Designer);
        }

        private void viewCodeToolStripMenuItem_Click(object sender, EventArgs e)
        {
            ShowWindowFrame(CreateTempSourceFile(false), VSConstants.LOGVIEWID_Code);
        }

        private string TemplateName(TreeNode leaf)
        {
            string ret = leaf.Text; 
            while (leaf.Parent != null)
            {
                if (leaf.Parent.Text != "子应用" && leaf.Parent.Text != "功能")
                    ret = leaf.Parent.Text + "-" + ret;
                leaf = leaf.Parent;
            }
            return ret;
        }

        /// <summary>
        /// Create a temp source file for current selected node so our designer can load it to the memory later.
        /// If createAlways is true, this method will always create a new file for current node.
        /// If temp file for current node exists and createAlways is false, a previously created temp file will
        /// be return.
        /// </summary>
        /// <param name="createAlways">If set to true, a new temp file will be created always. If set to false
        /// previously created temp file will be return if exists.</param>
        /// <returns>The path to the temp file which contains the source code of current node.</returns>
        private string CreateTempSourceFile(bool createAlways)
        {
            string tag = this.treeView1.SelectedNode.Tag.ToString();
            string newTempFile;
            if (tempSourceFileDictionary.ContainsKey(tag) && !createAlways)
            {
                return tempSourceFileDictionary[tag];
                //newTempFile = tempSourceFileDictionary[tag];
            }
            /*the below list contains all the file allow to be opened and edited*/
            //APIDXX : application extension prof xsl template
            //APIDXV : application extension prof vm  template
            //APIDXT : application extension prof Txt template
            //APIDXH : application extension prof Html template
            //FPIDXX : function extension prof xsl template
            //FPIDXV : function extension prof vm  template
            //FPIDXT : function extension prof Txt template
            //FPIDXH : function extension prof Html template
            //FPIDB : adapter type
            //FPIDD : data template
            //FPIDM : adapter template
            newTempFile = Path.GetTempPath();
            newTempFile += TemplateName(treeView1.SelectedNode);
            if (tag.StartsWith("APIDX"))
            {
                string[] ids = tag.Substring(6).Split(";".ToCharArray(), StringSplitOptions.RemoveEmptyEntries);
                int appId = int.Parse(ids[0]);
                int appProfId = int.Parse(ids[1]);
                Logger.Output(string.Format(@"Trying to get the conenct of {0}\{1}(ApplicationId\ApplicationProfId)", appId, appProfId));
                ApplicationProfTable applicationProf = Workspace.GetDatabaseLogic().GetApplicationProfTableDataByAppID(appId).SingleOrDefault(ap
                    => ap.APP_PROF_ID == appProfId);
                Debug.Assert(applicationProf != null);
                if(tag.StartsWith("APIDXX"))
                {
                    newTempFile += ".xsl";
                }
                else if (tag.StartsWith("APIDXV"))
                {
                    newTempFile += ".umc";
                }
                else if (tag.StartsWith("APIDXH"))
                {
                    newTempFile += ".htm";
                }
                else
                {
                    newTempFile += ".txt";
                }
                
                File.WriteAllText(newTempFile, applicationProf.APP_PROF_VALUE,System.Text.Encoding.UTF8);
            }
            else if (tag.StartsWith("FPIDX"))
            {
                string[] ids = tag.Substring(6).Split(";".ToCharArray(), StringSplitOptions.RemoveEmptyEntries);
                int functionId = int.Parse(ids[0]);
                int functionProfId = int.Parse(ids[1]);
                Logger.Output(string.Format(@"Trying to get the conenct of {0}\{1}(FunctionId\FunctionProfId)", functionId, functionProfId));

                FunctionProfTable functionProf = Workspace.GetDatabaseLogic().GetFunctionProfTableDataByFuncID(functionId).SingleOrDefault(fp
                    => fp.FUNC_PROF_ID == functionProfId);
                Debug.Assert(functionProf != null);
                if (tag.StartsWith("FPIDXX"))
                {
                    newTempFile += ".xsl";
                }
                else if (tag.StartsWith("FPIDXV"))
                {
                    newTempFile += ".umc";
                }
                else if (tag.StartsWith("FPIDXH"))
                {
                    newTempFile += ".htm";
                }
                else
                {
                    newTempFile += ".txt";
                }
                File.WriteAllText(newTempFile, functionProf.FUNC_PROF_VALUE, System.Text.Encoding.UTF8);
            }
            else if (tag.StartsWith("FPID"))
            {
                string[] ids = tag.Substring(5).Split(";".ToCharArray(), StringSplitOptions.RemoveEmptyEntries);
                int functionId = int.Parse(ids[0]);
                int functionProfId = int.Parse(ids[1]);
                Logger.Output(string.Format(@"Trying to get the conenct of {0}\{1}(FunctionId\FunctionProfId)", functionId, functionProfId));

                FunctionProfTable functionProf = Workspace.GetDatabaseLogic().GetFunctionProfTableDataByFuncID(functionId).SingleOrDefault(fp
                    => fp.FUNC_PROF_ID == functionProfId);
                Debug.Assert(functionProf != null);
                    
                newTempFile += ".umc";

                File.WriteAllText(newTempFile, functionProf.FUNC_PROF_VALUE, System.Text.Encoding.UTF8);
            }

            Logger.Output(string.Format("Temp file created: {0}", newTempFile));
            if (tempSourceFileDictionary.ContainsKey(tag))
            {
                tempSourceFileDictionary[tag] = newTempFile;
            }
            else
            {
                tempSourceFileDictionary.Add(tag, newTempFile);
            }

            // When we save changes to temp file, we need to write the content back to database
            FileSystemWatcher changeWatcher = new UmcFileSystemWatcher(new FileSystemEventHandler(changeWatcher_Changed));
            changeWatcher.Path = Path.GetDirectoryName(newTempFile);
            changeWatcher.Filter = Path.GetFileName(newTempFile);
            changeWatcher.NotifyFilter = NotifyFilters.LastWrite;
            changeWatcher.EnableRaisingEvents = true;
            watchers.Add(changeWatcher);

            return newTempFile;
        }

        void changeWatcher_Changed(object sender, FileSystemEventArgs e)
        {
            try
            {
                if (e.ChangeType == WatcherChangeTypes.Changed)
                {
                    string tag = tempSourceFileDictionary.Keys.SingleOrDefault(key
                        => tempSourceFileDictionary[key] == e.FullPath);
                    if (tag.StartsWith("APIDX"))
                    {
                        string[] ids = tag.Substring(6).Split(";".ToCharArray(), StringSplitOptions.RemoveEmptyEntries);
                        int appId = int.Parse(ids[0]);
                        int appProfId = int.Parse(ids[1]);
                        Logger.Output(string.Format("Write the content of [{0}] back to [{1}/{2}]", e.FullPath, appId, appProfId));
                        // Use a lock here to avoid too many concurrent database connection
                        lock (syncObj)
                        {
                            Workspace.GetDatabaseLogic().UpdateApplicationProfValue(appId, appProfId, File.ReadAllText(e.FullPath));
                        }
                    }
                    else if (tag.StartsWith("FPIDX"))
                    {
                        string[] ids = tag.Substring(6).Split(";".ToCharArray(), StringSplitOptions.RemoveEmptyEntries);
                        int functionId = int.Parse(ids[0]);
                        int functionProfId = int.Parse(ids[1]);
                        Logger.Output(string.Format("Write the content of [{0}] back to [{1}/{2}]", e.FullPath, functionId, functionProfId));
                        // Use a lock here to avoid too many concurrent database connection
                        lock (syncObj)
                        {
                            Workspace.GetDatabaseLogic().UpdateFunctionProfValue(functionId, functionProfId, File.ReadAllText(e.FullPath));
                        }
                    }
                    else if (tag.StartsWith("FPID"))
                    {
                        string[] ids = tag.Substring(5).Split(";".ToCharArray(), StringSplitOptions.RemoveEmptyEntries);
                        int functionId = int.Parse(ids[0]);
                        int functionProfId = int.Parse(ids[1]);
                        Logger.Output(string.Format("Write the content of [{0}] back to [{1}/{2}]", e.FullPath, functionId, functionProfId));
                        // Use a lock here to avoid too many concurrent database connection
                        lock (syncObj)
                        {
                            Workspace.GetDatabaseLogic().UpdateFunctionProfValue(functionId, functionProfId, File.ReadAllText(e.FullPath));
                        }
                    }
                }
            }
            catch(Exception ex)
            {
                Logger.Output(ex.Message);
                throw new Exception("changeWatcher_Changed expection", ex);
            }
        }

        // TODO:
        // #3. How to avoid switching to solution explore when new file opened
        // #5. Interaction between imagelist and listview
        // #6. How to avoid showing temp file name on tab
        // #7. Temp file is umc file even it is opened on a xml file
        // #9. Generate designer view at initialization
        // #10. Empty content connot be saved
        // #11. Implement menu for designer
        private void ShowWindowFrame(string mkDocument, Guid logicalViewGuid)
        {
            Logger.Output("Entering ShowWindowFrame");

            IVsUIShellOpenDocument shellOpenDocument = (IVsUIShellOpenDocument)GetService(typeof(IVsUIShellOpenDocument));
            Debug.Assert(shellOpenDocument != null);

            Microsoft.VisualStudio.OLE.Interop.IServiceProvider ppSP;
            IVsUIHierarchy ppHier;
            uint pitemid;
            IVsWindowFrame ppWindowFrame;

            int ret = shellOpenDocument.OpenDocumentViaProject(mkDocument,
                ref logicalViewGuid,
                out ppSP,
                out ppHier,
                out pitemid,
                out ppWindowFrame);
            ErrorHandler.ThrowOnFailure(ret);

            Debug.Assert(ppWindowFrame != null);
            ppWindowFrame.Show();

            Logger.Output("Leaving ShowWindowFrame");
        }

        public void RefreshData()
        {
            BuildTreeView();
        }

        private void treeView1_Click(object sender, EventArgs e)
        {
            DisplayProperty();
        }

        private void AddTemplateToolStripMenuItem_Click(object sender, EventArgs e)
        {
            //for the data template we should see if there is existed data template
            using (NewItemForm dialog = new NewItemForm("Template"))
            {
                dialog.ShowDialog();
                if (dialog.DialogResult == DialogResult.OK)
                {
                    string key_tag = "";
                    List<FunctionProfTable> funProfData = new List<FunctionProfTable>();
                    FunctionProfTable data = new FunctionProfTable();
                    data.FUNCTION_ID = Convert.ToInt32(this.selectedNode.Tag.ToString().Substring(3));
                    TreeNode tnTobeAdd = new TreeNode();
                    switch (dialog.selectedTemplateType)
                    {
                        case "DataTemplate":
                            data.FUNC_PROF_NAME = "DATA_TEMPLATE";
                            data.FUNC_PROF_VALUE = string.Empty;
                            key_tag = "FPIDD";
                            tnTobeAdd.Text = "Data";
                            tnTobeAdd.ImageIndex = (int)AppExpImageList.TempData;
                            tnTobeAdd.SelectedImageIndex = (int)AppExpImageList.TempDataSelected;
                            tnTobeAdd.Tag = key_tag;
                            break;
                        case "AdapterTemplate":
                            data.FUNC_PROF_NAME = "MOBILE_TEMPLATE";
                            data.FUNC_PROF_VALUE = string.Empty;
                            data.CLIENT_SYS_TYPE = dialog.cmbAdapterTmpName.SelectedItem.ToString();
                            key_tag = "FPIDM";
                            tnTobeAdd.Text = data.CLIENT_SYS_TYPE;
                            tnTobeAdd.ImageIndex = (int)AppExpImageList.TempAdapter;
                            tnTobeAdd.SelectedImageIndex = (int)AppExpImageList.TempAdapterSelected;
                            tnTobeAdd.Tag = key_tag;
                            break;
                        //case "XSLTemplate":
                        //    data.FUNC_PROF_NAME = dialog.nameTB.Text;
                        //    data.FUNC_PROF_VALUE = "<xml>";
                        //    key_tag = "FPIDX";
                        //    break;
                        default :
                            break;
                    }
                    if (dialog.selectedTemplateType == "DataTemplate" && Workspace.GetDatabaseLogic().DataTemplateIsExists(data.FUNCTION_ID))
                    {
                        MessageBox.Show("该功能已存在数据模板，只能创建一个数据模板！","提示",MessageBoxButtons.OK);
                    }
                    else
                    {
                        int lastid = 0;
                        funProfData.Add(data);
                        Workspace.GetDatabaseLogic().InsertFunctionProfTableData(funProfData, ref lastid);
                        tnTobeAdd.Tag += string.Format("{0};{1}", data.FUNCTION_ID,lastid);
                        if(key_tag == "FPIDD")
                            this.selectedNode.Nodes[1].Nodes.Add(tnTobeAdd);
                        else
                            this.selectedNode.Nodes[2].Nodes.Add(tnTobeAdd);

                        //BuildTreeView();
                        SelectAndExpandOrOpen(tnTobeAdd.Tag.ToString());
                    }
                }
            }
        }

        //add function prof click
        private void AddFunctionProf_Click(object sender, EventArgs e)
        {
            using (NewProfForm dialog = new NewProfForm())
            {
                dialog.ShowDialog();
                if (dialog.DialogResult == DialogResult.OK)
                {
                    //contruct a FunctionProfTable object
                    FunctionProfTable data = new FunctionProfTable();
                    List<FunctionProfTable> funProfData = new List<FunctionProfTable>();
                    data.FUNCTION_ID = Convert.ToInt32(this.selectedNode.Tag.ToString().Substring(3));
                    data.FUNC_PROF_NAME = dialog.Key;
                    data.FUNC_PROF_VALUE = dialog.Value;
                    data.FUNC_PROF_TYPE = dialog.TypeName;
                    string key_tag = string.Empty;                    
                    TreeNode tnTobeAdd = new TreeNode();
                    tnTobeAdd.Text = data.FUNC_PROF_NAME;
                    if(data.FUNC_PROF_TYPE == "xsl")
                    {
                        tnTobeAdd.ImageIndex = (int)AppExpImageList.TempXslt;
                        tnTobeAdd.SelectedImageIndex = (int)AppExpImageList.TempXsltSelected;
                        key_tag = "FPIDXX";
                    }
                    else if (data.FUNC_PROF_TYPE == "vm")
                    {
                        tnTobeAdd.ImageIndex = (int)AppExpImageList.TempVm;
                        tnTobeAdd.SelectedImageIndex = (int)AppExpImageList.TempVmSelected;
                        key_tag = "FPIDXV";
                    }
                    else if (data.FUNC_PROF_TYPE == "html")
                    {
                        tnTobeAdd.ImageIndex = (int)AppExpImageList.TempHtml;
                        tnTobeAdd.SelectedImageIndex = (int)AppExpImageList.TempHtmlSelected;
                        key_tag = "FPIDXH";
                    }
                    else
                    {
                        tnTobeAdd.ImageIndex = (int)AppExpImageList.TempTxt;
                        tnTobeAdd.SelectedImageIndex = (int)AppExpImageList.TempTxtSelected;
                        key_tag = "FPIDXT";
                    }
                    tnTobeAdd.Tag = key_tag;
                    
                    //see if the key is unique
                    if (Workspace.GetDatabaseLogic().FunctionExProfIsExists(data))
                    {
                        MessageBox.Show("The Key exists in the function , you must change another Key!", "提示", MessageBoxButtons.OK);
                    }
                    else
                    {
                        int lastid = 0;
                        funProfData.Add(data);
                        Workspace.GetDatabaseLogic().InsertFunctionProfTableData(funProfData, ref lastid);
                        tnTobeAdd.Tag += string.Format("{0};{1}", data.FUNCTION_ID, lastid);
                        this.selectedNode.Nodes[3].Nodes.Add(tnTobeAdd);
                        //BuildTreeView();
                        //auto open the extension prof editor
                        //string prefix = "FPIDX" + dialog.TypeName.Substring(0, 1).ToUpper();
                        SelectAndExpandOrOpen(tnTobeAdd.Tag.ToString());
                    }
                }
            }
        }

        //add application prof click
        private void AddAppProf_Click(object sender, EventArgs e)
        {
            using (NewProfForm dialog = new NewProfForm())
            {
                dialog.ShowDialog();
                if (dialog.DialogResult == DialogResult.OK)
                {
                    //contruct a FunctionProfTable object
                    ApplicationProfTable data = new ApplicationProfTable();
                    List<ApplicationProfTable> appProfData = new List<ApplicationProfTable>();
                    data.APP_ID = Convert.ToInt32(this.selectedNode.Tag.ToString());
                    data.APP_PROF_NAME = dialog.Key;
                    data.APP_PROF_VALUE = dialog.Value;
                    data.APP_PROF_TYPE = dialog.TypeName;
                    string key_tag = string.Empty;
                    TreeNode tnTobeAdd = new TreeNode();
                    tnTobeAdd.Text = data.APP_PROF_NAME;
                    if (data.APP_PROF_TYPE == "xsl")
                    {
                        tnTobeAdd.ImageIndex = (int)AppExpImageList.TempXslt;
                        tnTobeAdd.SelectedImageIndex = (int)AppExpImageList.TempXsltSelected;
                        key_tag = "APIDXX";
                    }
                    else if (data.APP_PROF_TYPE == "vm")
                    {
                        tnTobeAdd.ImageIndex = (int)AppExpImageList.TempVm;
                        tnTobeAdd.SelectedImageIndex = (int)AppExpImageList.TempVmSelected;
                        key_tag = "APIDXV";
                    }
                    else if (data.APP_PROF_TYPE == "html")
                    {
                        tnTobeAdd.ImageIndex = (int)AppExpImageList.TempHtml;
                        tnTobeAdd.SelectedImageIndex = (int)AppExpImageList.TempHtmlSelected;
                        key_tag = "APIDXH";
                    }
                    else
                    {
                        tnTobeAdd.ImageIndex = (int)AppExpImageList.TempTxt;
                        tnTobeAdd.SelectedImageIndex = (int)AppExpImageList.TempTxtSelected;
                        key_tag = "APIDXT";
                    }
                    tnTobeAdd.Tag = key_tag;
                    //see if the key is unique
                    if (Workspace.GetDatabaseLogic().ApplicationExProfIsExists(data))
                    {
                        MessageBox.Show("The Key exists in the application , you must change another Key!", "提示", MessageBoxButtons.OK);
                    }
                    else
                    {
                        int lastid = 0;
                        appProfData.Add(data);
                        Workspace.GetDatabaseLogic().InsertApplicationProfTableData(appProfData, ref lastid);
                        tnTobeAdd.Tag += string.Format("{0};{1}", data.APP_ID, lastid);
                        this.selectedNode.Nodes[2].Nodes.Add(tnTobeAdd);
                        //BuildTreeView();
                        //auto open the extension prof editor
                        //string prefix = "APIDX" + dialog.TypeName.Substring(0, 1).ToUpper();
                        SelectAndExpandOrOpen(tnTobeAdd.Tag.ToString());
                    }
                }
            }
        }





        private void addDataTempToolStripMenuItem_Click(object sender, EventArgs e)
        {
            //if (this.selectedNode.Nodes[1].Nodes.Count == 1)
            //{
            //    MessageBox.Show(string.Format(Resources.DataTempExistedWarning, this.selectedNode.Text), Resources.WarningCaption);
            //}
            //else
            //{
            //    using (NewItemForm dialog = new NewItemForm("DataTemplate"))
            //    {
            //        dialog.categoryTV.SelectedNode = dialog.categoryTV.Nodes[2].Nodes[0];
            //        dialog.ShowDialog();
            //        if (dialog.DialogResult == DialogResult.OK)
            //        {
            //            List<FunctionProfTable> funProfData = new List<FunctionProfTable>();
            //            FunctionProfTable data = new FunctionProfTable();
            //            data.FUNC_PROF_NAME = "DATA_TEMPLATE";
            //            data.FUNC_PROF_VALUE = string.Empty;
            //            data.FUNCTION_ID = Convert.ToInt32(this.selectedNode.Tag.ToString().Substring(3));
            //            funProfData.Add(data);
            //            BuildTreeView();
            //        }
            //    }
            //}
        }

        private void addAdapterTempToolStripMenuItem_Click(object sender, EventArgs e)
        {
            //using (NewItemForm dialog = new NewItemForm("AdapteTemplate"))
            //{
            //    dialog.categoryTV.SelectedNode = dialog.categoryTV.Nodes[2].Nodes[1];
            //    dialog.ShowDialog();
            //    if (dialog.DialogResult == DialogResult.OK)
            //    {
            //        List<FunctionProfTable> funProfData = new List<FunctionProfTable>();
            //        FunctionProfTable data = new FunctionProfTable();
            //        data.FUNC_PROF_NAME = "MOBILE_TEMPLATE";
            //        data.FUNC_PROF_VALUE = string.Empty;
            //        data.FUNCTION_ID = Convert.ToInt32(this.selectedNode.Tag.ToString().Substring(3));
            //        funProfData.Add(data);
            //        BuildTreeView();
            //    }
            //}
        }

        private void addXSLTempToolStripMenuItem_Click(object sender, EventArgs e)
        {
            //using (NewItemForm dialog = new NewItemForm())
            //{
            //    dialog.categoryTV.SelectedNode = dialog.categoryTV.Nodes[2].Nodes[2];
            //    dialog.ShowDialog();
            //    if (dialog.DialogResult == DialogResult.OK)
            //    {
            //        List<FunctionProfTable> funProfData = new List<FunctionProfTable>();
            //        FunctionProfTable data = new FunctionProfTable();
            //        data.FUNC_PROF_NAME = dialog.nameTB.Text;
            //        data.FUNC_PROF_VALUE = "<xml>";
            //        data.FUNCTION_ID = Convert.ToInt32(this.selectedNode.Tag.ToString().Substring(3));
            //        funProfData.Add(data);
            //        BuildTreeView();
            //    }
            //}
        }

        public enum AppExpImageList
        { 
            AppCat = 0,
            AppCatSelected = AppCat,

            FunCat = 1,
            FunCatSelected = FunCat,

            Application = 2,
            ApplicationSelected = Application,

            Function = 3,
            FunctionSelected = Function,

            Templates = 4,
            TemplatesSelected = Templates,

            // Templates
            TempBasic = 5,
            TempBasicSelected = TempBasic,

            TempData = 5,
            TempDataSelected = TempData,

            TempAdapter = 6,
            TempAdapterSelected = TempAdapter,

            TempXslt = 7,
            TempXsltSelected = TempXslt,

            TempVm = 8,
            TempVmSelected = TempVm,

            TempTxt = 9,
            TempTxtSelected = TempTxt,

            TempHtml = 10,
            TempHtmlSelected = TempHtml,

            ExProfCat = 11,
            ExProfCatSelected = ExProfCat
            

        }

        public void DisconnectWorkspace()
        {
            this.treeView1.Nodes.Clear();
        }




    }
}
